/**
 * @file   Boolean.cpp
 * @author Djuro Drljaca (djurodrljaca@gmail.com)
 * @date   2014-04-18
 * @brief  DON data type object: Boolean
 *
 * Copyright 2014  Djuro Drljaca (djurodrljaca@gmail.com)
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library.  If not, see <http://www.gnu.org/licenses/>.
 */

#include <DON/Core/DataType/Boolean.h>
#include <QtCore/QByteArray>

using namespace DON::Core::DataType;

class Boolean::Private
{
public:
    Private()
        : value(false)
    { }

    bool value;
};

Boolean::Boolean()
    : AbstractDataType(),
      d(new Private())
{
}

Boolean::Boolean(const Boolean &other)
    : AbstractDataType(),
      d(new Private())
{
    d->value = other.d->value;
}

Boolean::~Boolean()
{
    delete d;
}

Boolean & Boolean::operator=(const Boolean &other)
{
    d->value = other.d->value;

    return *this;
}

AbstractDataType * Boolean::clone() const
{
    return new Boolean(*this);
}

DataType Boolean::getDataType() const
{
    return DataType_Boolean;
}

bool Boolean::getValue() const
{
    return d->value;
}

void Boolean::setValue(const bool value)
{
    d->value = value;
}

bool Boolean::fromBinary(const QByteArray &data, const int startIndex, int *size)
{
    bool value = false;
    bool success = false;

    if ((data.size() > 0) &&
        (startIndex >= 0) &&
        (startIndex < data.size()))
    {
        value = Boolean::fromBinary(data.at(startIndex), &success);
        success = true;
    }

    if (success)
    {
        d->value = value;

        if (size != NULL)
        {
            *size = 1;
        }
    }

    return success;
}

QByteArray Boolean::toBinary() const
{
    return QByteArray(1, Boolean::toBinary(d->value));
}

Boolean * Boolean::fromAbstractDataType(AbstractDataType *instance)
{
    Boolean *outputInstance = NULL;

    if (instance != NULL)
    {
        if (instance->getDataType() == DataType_Boolean)
        {
            outputInstance = static_cast<Boolean *>(instance);
        }
    }

    return outputInstance;
}

bool Boolean::fromBinary(const char data, bool *ok)
{
    bool value = false;
    bool success = false;

    switch (data)
    {
        // False
        case 0x00:
        {
            value = false;
            success = true;
            break;
        }

        // True
        case 0x01:
        {
            value = true;
            success = true;
            break;
        }

        // Invalid value
        default:
        {
            value = false;
            success = false;
            break;
        }
    }

    if (ok != NULL)
    {
        *ok = success;
    }

    return value;
}

char Boolean::toBinary(const bool value)
{
    char data = 0x00;

    if (value)
    {
        data = 0x01;
    }

    return data;
}
